use serde::Serialize;
use serde_json::Value;
use std::fmt::Debug;
use crate::extends::core::db::data_converter::DataConverter;

/// 插入语句构造器
pub struct InsertBuilder;

impl InsertBuilder {
    /// 构建插入语句
    ///
    /// # 参数
    /// * `table_name` - 表名
    /// * `data` - 要插入的数据，必须实现 `Sized`、`Debug` 和 `Serialize` 特性
    ///
    /// # 返回值
    /// 返回一个包含插入语句的字符串
    pub fn build<T>(table_name: &str, data: &T) -> String
        where
            T: Sized + Debug + Serialize,
    {
        let mut fields = vec![]; // 用于存储字段名
        let mut values = vec![]; // 用于存储对应的值
        let data_map = DataConverter::convert_to_map(data, false); // 将数据转换为哈希映射

        for (key, value) in data_map {
            fields.push(key.clone()); // 将字段名添加到字段列表
            values.push(Self::format_value(&key, &value)); // 格式化值并添加到值列表
        }

        // 生成插入语句
        format!(
            "INSERT INTO {} ({}) VALUES ({})",
            table_name,
            fields.join(", "),
            values.join(", ")
        )
    }

    /// 格式化值
    ///
    /// # 参数
    /// * `key` - 字段名
    /// * `value` - 对应的值
    ///
    /// # 返回值
    /// 返回格式化后的值的字符串
    fn format_value(key: &str, value: &Value) -> String {
        if key.ends_with("_at") {
            // 处理日期字段
            if let Some(date_str) = value.as_str() {
                let formatted_date = date_str.replace("T", " ").replace("Z", "");
                format!("'{}'", formatted_date)
            } else {
                "NULL".to_string()
            }
        } else {
            // 处理其他字段
            match value {
                Value::String(s) => format!("'{}'", s),
                Value::Number(n) => n.to_string(),
                Value::Bool(b) => b.to_string(),
                _ => "NULL".to_string(),
            }
        }
    }
}

fn main() {
    #[derive(Debug, Serialize)]
    struct User {
        id: Option<String>,
        email: Option<String>,
        first_name: Option<String>,
        last_name: Option<String>,
        username: Option<String>,
    }

    let user = User {
        id: Some("1".to_string()),
        email: Some("test@example.com".to_string()),
        first_name: Some("John".to_string()),
        last_name: Some("Doe".to_string()),
        username: Some("johndoe".to_string()),
    };

    // 构建插入语句
    let insert_sql = InsertBuilder::build("users", &user);
    log::info!("{}", insert_sql);
}
